package org.emavaj.sanguosha.model.card;



import java.util.List;

import org.emavaj.sanguosha.model.card.resource.CardResHelper;
import org.emavaj.sanguosha.model.exception.SGSException;
import org.emavaj.sanguosha.model.vo.CardVO;
import org.emavaj.sanguosha.view.gameview.GameFrame;
import org.w3c.dom.NamedNodeMap;

/**
 * 
 * eMavaj updated 20120915
 *
 */
public abstract class AbstractCard implements ICard {

	protected int suit;
	protected int color;
	protected String rank;
	protected String name;
	protected String className;
	
	public void init(NamedNodeMap typeMap, NamedNodeMap map) {
		init(CardResHelper.getSuitCode(map.getNamedItem("suit").getNodeValue()),
				this.suit > 2 ? ICard.COLOR_RED : ICard.COLOR_BLACK, map
						.getNamedItem("rank").getNodeValue(), typeMap
						.getNamedItem("type").getNodeValue(), typeMap
						.getNamedItem("class").getNodeValue());
	}
	
	protected void init(int suit, int color, String rank, String name, String className) {
		this.suit = suit;
		this.color = color;
		this.rank = rank;
		this.name = name;
		this.className = className;
	}
	
	/**
	 * 转换为VO
	 * @return
	 */
	public CardVO toCardVO() {
		
		CardVO card = new CardVO();
		card.setSuit(this.suit);
		card.setColor(this.color);
		card.setRank(this.rank);
		card.setName(this.name);
		card.setClassName(this.className);
		
		return card;
	}
	
	/**
	 * 从VO转换得到Card对象
	 * @param cardVO
	 */
	public void fromCardVO(CardVO cardVO) {
		init(cardVO.getSuit(), cardVO.getColor(), cardVO.getRank(),
				cardVO.getName(), cardVO.getClassName());
	}
	
	/**
	 * 是否需要对手反馈卡牌
	 * @return
	 */
	public abstract boolean needsFeedBack();
	
	/**
	 * 对手选中用于反馈的卡牌是否有用
	 * @param card
	 * @return
	 */
	public abstract boolean isFeedBackWork(AbstractCard card);
	
	public final boolean availableInTheState(GameFrame owner) {
		switch (owner.getDashboard().getCurrentPhase()) {
		case START:
			return avaInStartPhare(owner);
		case JUDGE:
			return avaInJudgePhare(owner);
		case DRAW:
			return avaInDrawPhare(owner);
		case PLAY:
			return avaInPlayPhare(owner);
		case DISCARD:
			return avaInDiscardPhare(owner);
		case FINISH:
			return avaInEndPhare(owner);
		case FEEDBACK:
			return avaInFeedBackPhare(owner);
		default:
			return false;
		}
	}
	
	protected boolean avaInStartPhare(GameFrame owner) {
		return false;
	}
	
	protected boolean avaInJudgePhare(GameFrame owner) {
		return false;
	}
	
	protected boolean avaInDrawPhare(GameFrame owner) {
		return false;
	}
	
	protected boolean avaInPlayPhare(GameFrame owner) {
		return false;
	}
	
	protected boolean avaInDiscardPhare(GameFrame owner) {
		return true;
	}
	
	protected boolean avaInEndPhare(GameFrame owner) {
		return false;
	}
	
	protected boolean avaInFeedBackPhare(GameFrame owner) {
		return owner.getDispatchInfo().checkFeedbackCard(this);
	}
	
	/**
	 * 确定该牌是否已经可以打出
	 * 应该被子类重构
	 * @param owner
	 * @return
	 */
	public boolean alreadyCanOffer(GameFrame owner) {
		return true;
	}

	public int getColor() {
		return color;
	}

	public int getSuit() {
		return suit;
	}

	public String getName() {
		return name;
	}

	public String getRank() {
		return rank;
	}

	public boolean isRed() {
		return color == ICard.COLOR_RED;
	}
	
	public String getClassName() {
		return className;
	}

	@Override
	public String toString() {
		return "AbstractCard{" +
				"suit=" + CardResHelper.getSuitString(suit) +
				//", color=" + color +
				", rank='" + rank + '\'' +
				", name='" + name + '\'' +
				", classname='" + className.substring(className.lastIndexOf(".")) + '\'' +
				'}';
	}

	@Override
	public boolean equals(Object obj) {
		if (obj instanceof AbstractCard) {
			AbstractCard card = (AbstractCard) obj;
			return card.suit == this.suit && card.rank.equals(rank)
					&& card.name.equals(name)
					&& card.className.equals(this.className);
		} else {
			return false;
		}
	}
	
	/**
	 * 是否是相同类别
	 * @param card
	 * @return
	 */
	public boolean kindEquals(AbstractCard card) {
		return card.name.equals(name);
	}
	
	/**
	 * 该牌指向的玩家数
	 * -1表示所有
	 * @return
	 */
	public int canSelectPlayerCount() {
		return 1;
	}
	
	/**
	 * 点亮牌可以选择的目标玩家
	 * @param owner
	 */
	public void canOfferTo(GameFrame owner) {
	}
	
	public void hitTaget(GameFrame owner) {
	}
	
	public boolean canOfferMore(List<AbstractCard> cardList) {
		return false;
	}
	
	public AbstractCard combineCard(List<AbstractCard> cardList) {
		throw new SGSException("combine card error!");
	}
}
